package com.example.rwq_test.leetcode;

import java.util.*;

/**
 * @Description: 数字的读法
 *
 * @Author：dingdang4D
 * @Date：2024/5/9
 */
public class NumberToWords {
    private static final String ZERO = "零";
    private static final String SMALL_ZERO = "负";
    private static final Map<Character, String> DIGITS_MAP = new HashMap<>();
    private static final Map<Integer, String> UNIT_MAP = new HashMap<>();
    private static final Map<Integer, String> BIG_UNIT_MAP = new HashMap<>();
    private static final Stack<String> RESULT = new Stack<>();

    static {
        DIGITS_MAP.put('0', "零");
        DIGITS_MAP.put('1', "一");
        DIGITS_MAP.put('2', "二");
        DIGITS_MAP.put('3', "三");
        DIGITS_MAP.put('4', "四");
        DIGITS_MAP.put('5', "五");
        DIGITS_MAP.put('6', "六");
        DIGITS_MAP.put('7', "七");
        DIGITS_MAP.put('8', "八");
        DIGITS_MAP.put('9', "九");

        UNIT_MAP.put(0, "");
        UNIT_MAP.put(1, "十");
        UNIT_MAP.put(2, "百");
        UNIT_MAP.put(3, "千");

        BIG_UNIT_MAP.put(0, "");
        BIG_UNIT_MAP.put(1, "万");
        BIG_UNIT_MAP.put(2, "亿");
    }

    public static void main(String[] args) {
//        int number = Integer.MAX_VALUE;
//        int number = 0;
//        int number = 1000504020;
        int number = -1000504020;
        convertToWords(number);
        System.out.print("读法：");
        while (!RESULT.empty()) {
            System.out.print(RESULT.pop());
        }
    }

    public static void convertToWords(Integer number) {
        if (number == 0) {
            RESULT.push(ZERO);
            return;
        }
        String numStr = null;
        Boolean smallZero = false;
        if (number < 0) {
            numStr = String.valueOf(Math.abs(number));
            smallZero = true;
        } else {
            numStr = String.valueOf(number);
        }
        for (int i = 0; i < numStr.length(); i += 4) {
            Integer start = Math.max(0, numStr.length() - i - 4);
            Integer end = numStr.length() - i;
            String subNumStr = numStr.substring(start, end);
            RESULT.push(BIG_UNIT_MAP.get(i / 4));
            convertSubToWords(subNumStr);
            if (Objects.equals(RESULT.peek(), ZERO)) {
                RESULT.pop();
            }
        }
        if (smallZero) {
            RESULT.push(SMALL_ZERO);
        }
    }

    public static void convertSubToWords(String subStr) {
        Deque<String> temp = new ArrayDeque<>();
        for (int i = subStr.length() - 1; i >= 0; i--) {
            char digit = subStr.charAt(i);
            if (digit == '0' && !temp.isEmpty() && !Objects.equals(temp.peek(), ZERO)) {
                temp.push(ZERO);
            }
            if (digit != '0') {
                temp.push(UNIT_MAP.get(subStr.length() -1 - i));
                temp.push(DIGITS_MAP.get(digit));
            }
        }
        while (!temp.isEmpty()) {
            RESULT.push(temp.pollLast());
        }

    }
}
